import numpy as np


class AHP:
    def __init__(self, Matrix, weight, q):
        self.matrix = Matrix
        self.q = q

    def additiveConsistency(matrix, q):
        n = len(matrix)
        sum_1, sum_2 = 0, 0
        for i in range(0, n - 2):
            for j in range(i + 1, n - 1):
                for k in range(j + 1, n):
                    sum_1 += abs(matrix[i][j][0][0] ** q + matrix[j][k][0][0] ** q + matrix[i][k][1][1] ** q
                                 - matrix[i][j][1][1] ** q - matrix[j][k][1][1] ** q - matrix[i][k][0][0] ** q)
                    sum_2 += abs(matrix[i][j][0][1] ** q + matrix[j][k][0][1] ** q + matrix[i][k][1][0] ** q
                                 - matrix[i][j][1][0] ** q - matrix[j][k][1][0] ** q - matrix[i][k][0][1] ** q)
        if n > 2:
            CI_1 = (2 * sum_1) / (n * (n - 1) * (n - 2))
            CI_2 = (2 * sum_2) / (n * (n - 1) * (n - 2))
        else:
            CI_1 = (2 * sum_1) / (n * (n - 1))
            CI_2 = (2 * sum_2) / (n * (n - 1))
        if CI_1 <= 0.5 and CI_2 <= 0.5:  # 一致性极为宽松， 只能验证程序逻辑是正确的。
            # print("一致性检验通过")
            return True
        else:
            print("一致性检验失败")  # 一致性失败后的修复待写，只能重新给出数据
            return False

    def getDMatrix(self, matrix, q):
        """
        :param matrix: 对比矩阵
        :param q:
        :return: 区间得分矩阵
        """
        Dmatrix = []
        # for i in range(len(matrix)):
        #     D = []
        #     for k in range(len(matrix[0])):
        #         d1 = matrix[i][k][0][0] ** q - matrix[i][k][1][1] ** q
        #         d2 = matrix[i][k][0][1] ** q - matrix[i][k][1][0] ** q
        #         D.append([d1, d2])
        #     Dmatrix.append(D)
        for i in range(len(matrix)):
            D = []
            for k in range(len(matrix[0])):
                d1 = matrix[i][k][0][0] ** q - matrix[i][k][1][1] ** q
                d2 = matrix[i][k][0][1] ** q - matrix[i][k][1][0] ** q
                D.append([d1, d2])
            Dmatrix.append(D)
        # print("得分矩阵:", Dmatrix)
        return Dmatrix

    def getSMatrix(self, matrix, q):
        """

        :param matrix: 区间得分矩阵
        :param q:
        :return:区间乘法矩阵
        """
        SMatrix = []
        for i in range(len(matrix)):
            S = []
            for j in range(len(matrix[0])):
                s1 = pow((10 ** (2 * q - 1)) ** matrix[i][j][0], 1 / q)
                s2 = pow((10 ** (2 * q - 1)) ** matrix[i][j][1], 1 / q)  # (10 ** (2 * q - 1)有待优化
                # s1 = pow(math.e ** matrix[i][j][0], 1 / q)
                # s2 = pow(math.e ** matrix[i][j][1], 1 / q)  # (10 ** (2 * q - 1)有待优化
                S.append([s1, s2])
            SMatrix.append(S)
        # print("区间乘法矩阵:", SMatrix)
        return SMatrix

    def getIPMatrix(self, matrix):
        """

        :param matrix:区间乘法矩阵
        :return: 区间权重矩阵
        """
        IPMatrix = []
        s1 = 0
        s2 = 0
        for i in range(len(matrix)):
            for j in range(len(matrix[0])):
                s1 += matrix[i][j][0]
                s2 += matrix[i][j][1]
        for i in range(len(matrix)):
            u = 0
            v = 0
            for j in range(len(matrix[0])):
                u += matrix[i][j][0]
                v += matrix[i][j][1]
            IPMatrix.append([u / s2, v / s1])
        # print("区间权重向量:", IPMatrix)
        return IPMatrix

    def getPDMatrix(self, matrix):
        """

        :param matrix: 区间权重向量
        :return: 可能性度量矩阵
        """
        PDMatrix = []
        for i in range(len(matrix)):
            P = []
            for j in range(len(matrix)):
                l1 = matrix[i][1] - matrix[i][0]
                l2 = matrix[j][1] - matrix[j][0]
                p = min(l1 + l2, max(matrix[i][1] - matrix[j][0], 0)) / (l1 + l2)
                P.append(p)
            PDMatrix.append(P)
        # print("可能性度量矩阵:", PDMatrix)
        return PDMatrix

    def getWeightVector(self, matrix):
        """

        :param matrix: 可能性度量矩阵
        :return: 权重向量
        """
        n = len(matrix)
        weightMatrix = []
        for i in range(n):
            sum = 0
            for j in range(n):
                sum += matrix[i][j]
            weightMatrix.append((sum + n / 2 - 1) / n)
        # print("权重向量:", weightMatrix)
        count = 0
        for i in range(len(weightMatrix)):
            count += weightMatrix[i]
        for i in range(len(weightMatrix)):
            weightMatrix[i] = weightMatrix[i] / count
        # print("权重向量:", weightMatrix)
        return weightMatrix

    def getResult(self):
        if AHP.additiveConsistency(self.matrix, self.q):
            DMatrix = self.getDMatrix(self.matrix, self.q)
            SMatrix = self.getSMatrix(DMatrix, self.q)
            IPMatrix = self.getIPMatrix(SMatrix)
            PDMatrix = self.getPDMatrix(IPMatrix)
            weightVector = self.getWeightVector(PDMatrix)
            return weightVector
        pass


if __name__ == '__main__':
    data1 = np.array(
        [[([0.5, 0.5], [0.5, 0.5]), ([0.6, 0.7], [0.1, 0.3])],
         [([0.1, 0.3], [0.6, 0.7]), ([0.2, 0.3], [0.6, 0.7])]])
    ahp1 = AHP(data1, 3)
    result1 = ahp1.getResult()
    print(result1)
